'''
    Author: Nebiyou Yismaw

    This is a python code will use opencv to find use simple shapes such as lines
    and circles using hough tranform.
'''

import cv2
import numpy as np


def extract_lines():
    '''
        A function to extract lines from an image using hough transform
    '''
    # Read image
    img = cv2.imread('lanes.jpg', cv2.IMREAD_COLOR)
    # Convert the image to gray-scale
    gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    # Find the edges in the image using canny detector
    edges = cv2.Canny(gray, 50, 200)
    # Detect points that form a line
    lines = cv2.HoughLinesP(edges, 1, np.pi/180, 100, minLineLength=10, maxLineGap=250)
    # Draw lines on the image
    for line in lines:
        x1, y1, x2, y2 = line[0]
        cv2.line(img, (x1, y1), (x2, y2), (255, 0, 0), 3)
    # Show result
    cv2.imshow("Lines", img)
    cv2.waitKey(0)



def extract_circles():
    '''
        A function to extract circles from an image using hough transform
    '''
    # Read image as gray-scale
    img = cv2.imread('circles.jpg', cv2.IMREAD_COLOR)
    # Convert to gray-scale
    gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    # Blur the image to reduce noise
    img_blur = cv2.medianBlur(gray, 5)
    # Apply hough transform on the image
    circles = cv2.HoughCircles(img_blur, cv2.HOUGH_GRADIENT, 1, 50, param1=450, param2=10, minRadius=30, maxRadius=40)
    # Draw detected circles
    if circles is not None:
        circles = np.uint16(np.around(circles))
        for i in circles[0, :]:
            # Draw outer circle
            cv2.circle(img, (i[0], i[1]), i[2], (0, 255, 0), 2)
            # Draw inner circle
            cv2.circle(img, (i[0], i[1]), 2, (0, 0, 255), 3)
    cv2.imshow("Circles", img)
    cv2.waitKey(0)


def main():
    extract_lines()
    extract_circles()

if __name__=="__main__":
    main()
